package com.habdqn.studentmanager.util;

import java.text.SimpleDateFormat;
import java.time.DateTimeException;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;
import java.util.Calendar;
import java.util.Date;
import java.util.TimeZone;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * @author Administrator
 * 日期工具类
 * 2017年5月25日
 * 
 */
public final class DateUtil {
	
	private static final Logger logger = LoggerFactory.getLogger(DateUtil.class);
	
	/**
	 * 长度为19的格式化字符串
	 * yyyy-MM-dd hh:mm:ss
	 */
	public static final String FormatStr19 = "yyyy-MM-dd hh:mm:ss";
	
	/**
	 * 长度为10的格式化字符串
	 * yyyy-MM-dd
	 */
	public static final String FormatStr10 = "yyyy-MM-dd";
	
	/**
	 * 长度为14的格式化字符串
	 * yyyyMMddhhmmss
	 */
	public static final String FormatStr14 = "yyyyMMddhhmmss";
	
	/**
	 * 中国时区
	 */
	public static final TimeZone CHINA_TIMEZONE = TimeZone.getTimeZone("Asia/Shanghai"); 
	
	/**
	 * 时间格式化 hh:mm:ss
	 */
	public static final DateTimeFormatter LOCALTIME_FORMAT = DateTimeFormatter.ofPattern("HH:mm:ss");
	
	/**
	 * 增加或减去date的时间
	 * @param field the calendar field.
	 * @param the amount of date or time to be added to the field.
	 * @param date
	 */
	public static void add(int field, int amount, Date date) {
		Calendar calendar = Calendar.getInstance();
		calendar.setTime(date);
		calendar.add(field, amount);
		date.setTime(calendar.getTimeInMillis());
	}
	
	/**
	 * 将时间对象格式化为指定字符串
	 * @param date
	 * @param formatStr
	 * @return
	 */
	public static String format(Date date, String formatStr) {
		SimpleDateFormat sdf = new SimpleDateFormat(formatStr);
		try {
			return sdf.format(date);			
		}
		catch (Exception e) {
			logger.debug("转换时间失败, date:{}, format:{}", date, formatStr);
			return null;
		}
	}
	
	/**
	 * 将字符串解析成Date对象
	 * @param str
	 * @param formatStr
	 * @return
	 */
	public static Date parseDate(String str, String formatStr) {
		SimpleDateFormat sdf = new SimpleDateFormat(formatStr);
		try {
			return sdf.parse(str);			
		}
		catch (Exception e) {
			logger.debug("转换时间失败, source:{}, format:{}", str, formatStr);
			return null;
		}
	}
	
	/**
	 * 增加或减去date中指定的秒数
	 * @param amount
	 * @param date
	 */
	public static void addSeconds(int amount, Date date) {
		add(Calendar.SECOND, amount, date);
	}
	
	/**
	 * 增加或减去date中指定的分钟
	 * @param amount
	 * @param date
	 */
	public static void addMinutes(int amount, Date date) {
		add(Calendar.MINUTE, amount, date);
	}
	
	/**
	 * 增加或减去date中指定的小时
	 * @param amount
	 * @param date
	 */
	public static void addHours(int amount, Date date) {
		add(Calendar.HOUR_OF_DAY, amount, date);
	}
	
	/**
	 * 获取系统默认时区的当前时间
	 * @return
	 */
	public static Date now() {
		return now(TimeZone.getDefault());
	}
	
	/**
	 * 获取指定时区的当前时间
	 * @param zone
	 * @return
	 */
	public static Date now(TimeZone zone) {
		
		logger.debug("TimeZone:{}", zone.getID());
		
		Date date = new Date();
		Calendar calendar = Calendar.getInstance();
		calendar.setTime(date);
		
		// 计算新的偏移值
		int offsetTime = calendar.get(Calendar.ZONE_OFFSET) - zone.getRawOffset();
		int dstOffsetTime = calendar.get(Calendar.DST_OFFSET) - zone.getDSTSavings();
		logger.debug("ZONE_OFFSET:{} DST_OFFSET:{}", offsetTime, dstOffsetTime);
		
		calendar.add(Calendar.MILLISECOND, -(offsetTime + dstOffsetTime));
		return calendar.getTime();
	}
	
	/**
	 * 格式化时间
	 * @param time
	 * @param format
	 * @return
	 */
	public static String format(LocalTime time, DateTimeFormatter format) {
		
		try {
			return time.format(format);			
		}
		catch (DateTimeException e) {
			logger.debug("time:{} format:{}", time, format.toString(), e);
		}
		
		return null;
	}
	
	/**
	 * 将字符串转换成时间对象
	 * @param str
	 * @return
	 */
	public static LocalTime parseTime(String str) {
		
		try {
			return LocalTime.parse(str);			
		}
		catch (DateTimeParseException e) {
			logger.debug("parseTime:{}", str, e);
		}
		
		return null;
	}
}
